package cn.edu.swu.miniwebsvr.core;

import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class Server {
    private final Config config = Config.getInstance();// 获取单例配置实例
    private final ExecutorService threadPool = Executors.newFixedThreadPool(10);// 创建固定大小为10的线程池，处理并发请求
    // 启动服务器
    public void start() {
        // TODO: [222024321072057/王文薏] 实现 ServerSocket 的创建和监听
        try (ServerSocket serverSocket = new ServerSocket(config.getPort())) {
            System.out.println("MiniWebSvr 启动成功，监听端口：" + config.getPort());
            System.out.println("Web根目录：" + config.getWebRoot());

            // 持续监听客户端连接
            while (!serverSocket.isClosed()) {
                // 阻塞等待客户端连接
                Socket clientSocket = serverSocket.accept();
                System.out.println("接收到新的连接：" + clientSocket.getInetAddress());
                // 将请求处理任务提交到线程池
                threadPool.execute(new RequestProcessor(clientSocket));
            }
        } catch (IOException e) {
            System.err.println("服务器启动失败或运行异常: " + e.getMessage());
            // 发生异常时关闭线程池
            threadPool.shutdown();
            System.out.println("服务器已停止");
        }
    }
    // 请求处理线程类（实现Runnable接口）
    private static class RequestProcessor implements Runnable {
        private final Socket socket;// 客户端连接的Socket

        public RequestProcessor(Socket socket) {
            this.socket = socket;
        }

        @Override
        public void run() {
            // TODO: [222024321072057/王文薏] 完善请求处理流程，确保异常安全和资源关闭
            try {
                // 解析HTTP请求，封装为Parameter对象
                Parameter request = HttpParser.parse(socket.getInputStream());

                // 创建路由处理器，分发请求并处理
                Router router = new Router();
                router.route(request, socket.getOutputStream());

            } catch (Exception e) {
                System.err.println("请求处理异常: " + e.getMessage());
                // TODO: [222024321072057/王文薏] 可以在这里实现返回 500 错误页面的逻辑
                // 发生异常时返回500错误
                try {
                    if (socket.getOutputStream() != null) {
                        String errorMsg = "HTTP/1.1 500 Internal Server Error\r\n" +
                                "Content-Type: text/plain\r\n" +
                                "Content-Length: " + e.getMessage().length() + "\r\n" +
                                "\r\n" +
                                e.getMessage();
                        socket.getOutputStream().write(errorMsg.getBytes());
                        socket.getOutputStream().flush();
                    }
                } catch (IOException ex) {
                    System.err.println("错误响应发送失败：" + ex.getMessage());
                }
            } finally {
                // 确保所有资源最终被关闭
                try {
                    if (socket.getInputStream() != null) socket.getInputStream().close();
                } catch (IOException e) { /* ignore */ }
                try {
                    if (socket.getOutputStream() != null) socket.getOutputStream().close();
                } catch (IOException e) { /* ignore */}
                try {
                    if (socket != null) socket.close();
                } catch (IOException e) { /* ignore */ }
            }
        }
    }
    // 程序入口：启动服务器
    public static void main(String[] args) {
        Server server = new Server();
        server.start();
    }
}
